#include "formtown.h"
#include "ui_formtown.h"
#include "dlgstreetedit.h"
#include "dlghouseedit.h"
#include "lorismessenger.h"
#include "dlgapartmentedit.h"
#include <QResizeEvent>

FormTown::FormTown(QWidget *parent) :
    QWidget(parent),
    mp_dbms(NULL),
    mp_apn_model(NULL),
    mp_nav_sel_model(NULL),
    mp_ap_sel_model(NULL),
    m_current_nav_type(-1),
    mp_apartments_model(NULL),
    ui(new Ui::FormTown)
{
    ui->setupUi(this);
}

FormTown::~FormTown()
{
    delete ui;
}

void FormTown::set_dbms(HousingDBMS *p_dbms)
{
    mp_dbms = p_dbms;
    mp_apn_model = dynamic_cast<ModelContainer *>(mp_dbms->get_models())->get_town_model();
    mp_nav_sel_model = ui->treeView->selectionModel();
    connect(ui->btn_expand_tree, SIGNAL(clicked()), ui->treeView, SLOT(expandAll()));
    connect(ui->btn_collapse_tree, SIGNAL(clicked()), ui->treeView, SLOT(collapseAll()));

    mp_apartments_model = dynamic_cast<ModelContainer *>(mp_dbms->get_models())->get_apartments_model();

  //  ui->btn_select->hide();

    connect(ui->tableView, SIGNAL(activated(QModelIndex)), this, SLOT(apartment_item_activated(QModelIndex)));
    connect(ui->treeView, SIGNAL(doubleClicked(QModelIndex)), this, SLOT(nav_tree_edit_request(QModelIndex)));
    connect(ui->btn_new_street, SIGNAL(clicked()), this, SLOT(add_street()));
    connect(ui->btn_new_house, SIGNAL(clicked()), this, SLOT(add_house()));
    connect(ui->btn_del_nav_item, SIGNAL(clicked()), this, SLOT(remove_nav_tree_item()));

    connect(ui->btn_add_apartment, SIGNAL(clicked()), this, SLOT(add_apartment()));
    connect(ui->btn_del_apartment, SIGNAL(clicked()), this, SLOT(remove_apartment()));

    connect(ui->btn_select, SIGNAL(clicked()), this, SLOT(select_record()));
    connect(ui->splitter, SIGNAL(splitterMoved(int,int)), this, SLOT(splitter_resized()));

}


void FormTown::nav_tree_item_selected(const QModelIndex &index)
{
    m_current_nav_type = mp_apn_model->get_nav_type(index);
    mqv_current_nav_db_index = mp_apn_model->get_db_index(index);

    if(m_current_nav_type == IN_STREETS) mqv_current_s_db_index = mqv_current_nav_db_index;
    if(m_current_nav_type == IN_HOUSES) mqv_current_h_db_index = mqv_current_nav_db_index;

    QVariant qv_h_index = mp_apn_model->get_h_index(index);
    mp_apartments_model->set_active_h_index(qv_h_index);
    if(index.row() < 0) return;
    ui->tableView->scrollTo(mp_apartments_model->get_model_index_by_h_index(qv_h_index), QAbstractItemView::PositionAtTop);
   // lakhMsg()<<"current nav db_index selected"<<mqv_current_nav_db_index.toULongLong();
}

void FormTown::update_nav_model(bool do_not_load)
{
    ui->treeView->setModel(NULL);
    if(!do_not_load)
        mp_apn_model->load_data();
    ui->treeView->setModel(mp_apn_model);
    mp_nav_sel_model = ui->treeView->selectionModel();
    connect(mp_nav_sel_model, SIGNAL(currentRowChanged(QModelIndex,QModelIndex)), this, SLOT(nav_tree_item_selected(QModelIndex)));
    restore_nav_selection();
    ui->treeView->resizeColumnToContents(0);


    ui->tableView->setModel(NULL);
    if(!do_not_load)
        mp_apartments_model->load_data(mp_apn_model->get_h_indexes());
    ui->tableView->setModel(mp_apartments_model);
    mp_ap_sel_model = ui->tableView->selectionModel();
    connect(mp_ap_sel_model, SIGNAL(currentChanged(QModelIndex,QModelIndex)), this, SLOT(apartment_item_selected(QModelIndex)));
    restore_ap_selection();
    //ui->tableView->resizeColumnsToContents();

}

void FormTown::restore_nav_selection()
{
    if(m_current_nav_type == -1) return;
    QModelIndex index = mp_apn_model->createIndexFor(m_current_nav_type, mqv_current_nav_db_index);
    if(mp_nav_sel_model == NULL) return;
    mqv_current_h_db_index = mqv_current_s_db_index = mqv_current_nav_db_index = QVariant();
    mp_nav_sel_model->select(index, QItemSelectionModel::Select | QItemSelectionModel::Rows);
    ui->treeView->scrollTo(index);
}

void FormTown::apartment_item_selected(const QModelIndex &index)
{
    mqv_current_ap_db_index = mp_apartments_model->get_ap_db_index(index);
    mqh_current_ap_data = mp_apartments_model->get_ap_data(index);
    qDebug()<<"apartment selected"<<index.row();
    QVariant qv_h_index = mqh_current_ap_data.value(FLD_APDB_HSINDEX);
    QModelIndex h_mindex = mp_apn_model->createIndexFor(IN_HOUSES, qv_h_index);
    mp_nav_sel_model->clearSelection();
    mp_nav_sel_model->select(h_mindex, QItemSelectionModel::Select | QItemSelectionModel::Rows);
    mp_apartments_model->set_active_h_index(qv_h_index);
    ui->treeView->scrollTo(h_mindex,QAbstractItemView::PositionAtCenter);

}

void FormTown::apartment_item_activated(const QModelIndex &index)
{
    //mqv_current_ap_db_index = mp_apartments_model->get_ap_db_index(index);

    DlgApartmentEdit *p_ae = new DlgApartmentEdit();
    p_ae->set_dbms(mp_dbms);
    p_ae->set_data(mqh_current_ap_data);
    p_ae->set_focus_fld(mp_apartments_model->get_fld_by_mindex(index));
    if(p_ae->exec())
    {
        if(p_ae->is_changed())
        {
            mqh_current_ap_data = p_ae->get_data();
            mp_dbms->db_put(LAKDB_APARTMENTS, mqh_current_ap_data, mqv_current_ap_db_index);
            mp_apartments_model->update_data(index, mqh_current_ap_data);
            lakhMsg()<<RUSTR("Данные по жилым помещениям обновлены.");
            ui->tableView->setVisible(false);
            ui->tableView->setVisible(true);
        }
    }
    delete p_ae;
}

void FormTown::restore_ap_selection()
{
    QModelIndex index = mp_apartments_model->get_model_index_by_ap_index(mqv_current_ap_db_index);
    mp_ap_sel_model->select(index,QItemSelectionModel::Select|QItemSelectionModel::Rows);
    ui->tableView->scrollTo(index, QAbstractItemView::PositionAtCenter);
}

void FormTown::nav_tree_edit_request(const QModelIndex &index)
{
    SLEE_HDB_REC qh_data;
    int db_type = mp_apn_model->get_nav_type(index);
    QVariant qv_index = mp_apn_model->get_db_index(index);
    if(db_type == IN_STREETS)
    {
        DlgStreetEdit  *p_se = new DlgStreetEdit();
        p_se->set_dbms(mp_dbms);
        p_se->set_data(mp_dbms->get_data(LAKDB_STREETS, qv_index));
        if(p_se->exec())
        {
            if(p_se->is_changed())
            {
                qh_data = p_se->get_data();
                mp_dbms->db_put(LAKDB_STREETS, qh_data, qv_index);
                lakhMsg()<<RUSTR("Данные по улицам обновлены.");
            }

        }
        delete p_se;
    }
    if(db_type == IN_HOUSES)
    {
        DlgHouseEdit *p_he = new DlgHouseEdit();
        p_he->set_dbms(mp_dbms);
        p_he->set_data(mp_dbms->get_data(LAKDB_HOUSES, qv_index));
        if(p_he->exec())
        {
            if(p_he->is_changed())
            {
                qh_data = p_he->get_data();
                mp_dbms->db_put(LAKDB_HOUSES, qh_data, qv_index);
                lakhMsg()<<RUSTR("Данные по домам обновлены.");
            }
        }
        delete p_he;
    }
    ui->treeView->setVisible(false);
    ui->treeView->setVisible(true);
}


void FormTown::add_street()
{
    DlgStreetEdit * p_se = new DlgStreetEdit();
    p_se->set_dbms(mp_dbms);
    p_se->set_data(SLEE_HDB_REC());
    if(p_se->exec())
    {
        if(p_se->is_changed())
        {
            SLEE_HDB_REC qh_data = p_se->get_data();
            mp_dbms->db_put(LAKDB_STREETS, qh_data);
            lakhMsg()<<RUSTR("Новая улица внесена в базу.");
            update_nav_model();
        }
    }
    delete p_se;
}

void FormTown::add_house()
{
   if(mqv_current_s_db_index.isNull())
   {
       lakhMsgE()<<RUSTR("Ошибка. Невозможно внести новый дом в базу. Не  выбрана улица.");
       return;
   }
   SLEE_HDB_REC qh_data;
   qh_data[FLD_HSDB_STINDEX] = mqv_current_s_db_index;
    DlgHouseEdit *p_he = new DlgHouseEdit();
    p_he->set_dbms(mp_dbms);
    p_he->set_data(qh_data);
    if(p_he->exec())
    {
        if(p_he->is_changed())
        {
            qh_data = p_he->get_data();
            mp_dbms->db_put(LAKDB_HOUSES, qh_data);
            lakhMsg()<<RUSTR("Новый дом внесен в базу.");
            update_nav_model();
        }
    }
    delete p_he;
}


void FormTown::remove_nav_tree_item()
{
    SLEE_HDB_REC qh_data;
    if(mqv_current_nav_db_index.isNull())
    {
        lakhMsg()<<RUSTR("Не выбран элемент для удаления.");
    }
    if(m_current_nav_type == IN_STREETS)
    {
        if(!mp_dbms->can_remove(LAKDB_STREETS, mqv_current_s_db_index)) return;
        qh_data = mp_dbms->get_data(LAKDB_STREETS, mqv_current_s_db_index);
        mp_dbms->get_db(LAKDB_STREETS)->removeData(qh_data,mqv_current_s_db_index);
    }
    if(m_current_nav_type == IN_HOUSES)
    {
        if(!mp_dbms->can_remove(LAKDB_HOUSES, mqv_current_h_db_index)) return;
        SLEE_HDB_REC qh_data = mp_dbms->get_data(LAKDB_HOUSES, mqv_current_h_db_index);
        mp_dbms->get_db(LAKDB_HOUSES)->removeData(qh_data,mqv_current_h_db_index);
    }
    update_nav_model();
}


void FormTown::remove_apartment()
{
        if(mqv_current_ap_db_index.isNull())
        {
            lakhMsgE()<<RUSTR("Ошибка! Не выбрано жилое помещение.");
            return;
        }
        if(!mp_dbms->can_remove(LAKDB_APARTMENTS, mqv_current_ap_db_index)) return;
        mp_dbms->get_db(LAKDB_APARTMENTS)->removeData(mqh_current_ap_data, mqv_current_ap_db_index);
        lakhMsg()<<RUSTR("Данные по жилому помещению удалены.");
        mqv_current_ap_db_index = QVariant();
        mqh_current_ap_data = SLEE_HDB_REC();
        update_nav_model();
}

void FormTown::add_apartment()
{
    if(mqv_current_h_db_index.isNull())
    {
         lakhMsgE()<<RUSTR("Ошибка! Не выбран дом.");
         return;
    }
    SLEE_HDB_REC qh_data;
    qh_data[FLD_APDB_HSINDEX] = mqv_current_h_db_index;
    DlgApartmentEdit *p_ae = new DlgApartmentEdit();
    p_ae->set_dbms(mp_dbms);
    p_ae->set_data(qh_data);
    if(p_ae->exec())
    {
        if(p_ae->is_changed())
        {
            qh_data = p_ae->get_data();
            mp_dbms->db_put(LAKDB_APARTMENTS, qh_data);
            lakhMsg()<<RUSTR("Данные по жилому помещению внесены в БД.");
            update_nav_model();
        }
    }
    delete p_ae;
}

void FormTown::select_record()
{
    emit record_selected(mqv_current_ap_db_index);
    hide();
}

void FormTown::enable_selection()
{
    ui->btn_select->setVisible(true);
}


void FormTown::set_ap_selection(const QVariant &qv_ap_index)
{
    QModelIndex mod_index = mp_apartments_model->get_model_index_by_ap_index(qv_ap_index);
    mp_ap_sel_model->select(mod_index, QItemSelectionModel::Select);
    apartment_item_selected(mod_index);
    ui->tableView->scrollTo(mod_index, QAbstractItemView::PositionAtCenter);
}

void FormTown::hide_sel_btn()
{
    ui->btn_select->hide();
}


void FormTown::resizeEvent(QResizeEvent *p_e)
{

   splitter_resized();
    QWidget::resizeEvent(p_e);
}

void FormTown::showEvent(QShowEvent *p_e)
{
    splitter_resized();
    QWidget::showEvent(p_e);
}

void FormTown::splitter_resized()
{
    //    case 0: str = RUSTR("Адрес");  //house address        30
    //    case 1: str = RUSTR("Номер"); //apartment number    10
    //    case 2: str = RUSTR("Кол-во\nкомнат");                    10
    //    case 3: str = RUSTR("Общая\nпл.(кв.м.)");               15
    //    case 4: str = RUSTR("Жилая\nпл.(кв.м.)");                15
    //    case 5: str = RUSTR("Комментарии");                       20

    int x = ui->tableView->size().width();//p_e->size().width();
    ui->tableView->setColumnWidth(0, x*30/100);
    ui->tableView->setColumnWidth(1, x/10);
    ui->tableView->setColumnWidth(2, x/10);
    ui->tableView->setColumnWidth(3, x*15/100);
    ui->tableView->setColumnWidth(4, x*15/100);
    ui->tableView->setColumnWidth(5, x/5);
}
